home *** CD-ROM | disk | FTP | other *** search
/ Linux Cubed Series 8: LINUX Games / Linux Cubed Series 8 - LINUX Games.iso / games / video / fly8111-.000 / fly8111- / fly8 / parms / expr.awk < prev    next >
Text File  |  1979-12-31  |  6KB  |  347 lines

  1. # --------------------------------- expr.awk -----------------------------------
  2.  
  3. #
  4. # This is part of the flight simulator 'fly8'.
  5. # Author: Eyal Lebedinsky (eyal@ise.canberra.edu.au).
  6. #
  7.  
  8. #
  9. # Convert a (cpp processed) object description to a simple list of numbers.
  10. # The input should be a comma separated list of quadruplets.
  11. # Evaluates expressions using '+ - * / % ( )'. All other characters are 
  12. # removed. A vertex count is added to the beginning.
  13. # Also does the nav data file. Accepts string too.
  14. #
  15.  
  16.  
  17. BEGIN    {
  18.     hextab["0"] = 0
  19.     hextab["1"] = 1
  20.     hextab["2"] = 2
  21.     hextab["3"] = 3
  22.     hextab["4"] = 4
  23.     hextab["5"] = 5
  24.     hextab["6"] = 6
  25.     hextab["7"] = 7
  26.     hextab["8"] = 8
  27.     hextab["9"] = 9
  28.     hextab["a"] = 10
  29.     hextab["b"] = 11
  30.     hextab["c"] = 12
  31.     hextab["d"] = 13
  32.     hextab["e"] = 14
  33.     hextab["f"] = 15
  34.     hextab["A"] = 10
  35.     hextab["B"] = 11
  36.     hextab["C"] = 12
  37.     hextab["D"] = 13
  38.     hextab["E"] = 14
  39.     hextab["F"] = 15
  40.  
  41.     fin  = ARGV[1]
  42.     fout = ARGV[2]
  43.  
  44.     fname = fin
  45.  
  46.     lineno = 0
  47.     advance()
  48.     while (1) {
  49.         if (tok ~ /^\".*/) {
  50.             printf ("%s\n", tok) >fout
  51.             advance()
  52.         } else {
  53.             x = int(expression())
  54.             printf ("%d\n", x) >fout
  55.         }
  56.         ++n
  57.         if (tok == "(eof)")
  58.             break;
  59.         eat(",")
  60.     }
  61.     
  62.     close(fin)
  63.     close(fout)
  64. }
  65.  
  66. function advance() {
  67.     if (tok == "(eof)")
  68.         return tok
  69.     while (1) {
  70.         while (1) {
  71.             if (length(line) == 0)
  72.                 ++lineno
  73.             else if (substr(line,1,1) == "#") {
  74.                 split(line,a)
  75.                 if (a[1] == "#line") {
  76.                     lineno = a[2]+0
  77.                 } else if (a[1] == "#") {
  78.                     lineno = a[2]+0
  79.                     if (a[3] != "")
  80.                         fname = a[3]
  81.                 } else
  82.                     ++lineno
  83.             } else
  84.                 break
  85.             if (getline line <fin == 0)
  86.                 return tok = "(eof)"
  87.         }
  88.         if (match(line, /^[ \t;\n{}]/))
  89.                 line = substr(line, 2)
  90.         else
  91.                 break
  92.     }
  93.     if (match(line, /^0[xX][0-9a-fA-F]+/) || match(line, /^[.0-9]+/) ||
  94.         match(line, /^(<=|==|!=|>=|\|\||&&|>>|<<)/) ||
  95.         match(line, /^\".*\"/) ||
  96.         match(line, /^./)) {
  97.             tok = substr(line, 1, RLENGTH)
  98.             line = substr(line, RLENGTH+1)
  99.             return tok
  100.     }
  101.     error(fname "(" lineno ") unrecognized token")
  102. }
  103.  
  104. function eat(s) {
  105.     if (tok != s)
  106.         error(fname "(" lineno ") saw \"" tok "\" expected \"" s "\"")
  107.     advance()
  108. }
  109.  
  110. function error(s) {
  111.     print "Error: " s
  112.     exit 1
  113. }
  114.  
  115. function statement(  e, e1, e2) {
  116.     return
  117. }
  118.  
  119. function expression(  e, e1, e2) {
  120.     e = logical_or()
  121.     if (tok == "?") {
  122.         advance()
  123.         e1 = expression()
  124.         eat(":")
  125.         e2 = expression()
  126.         if (e)
  127.             e = e1
  128.         else
  129.             e = e2
  130. # This fails!:    e = e ? e1 : e2
  131.     }
  132.     return e
  133. }
  134.  
  135. function logical_or(  e, e1) {
  136.     e = logical_and()
  137.     while (tok == "||") {
  138.         advance()
  139.         e1 = logical_and()
  140.         e = e || e1
  141.     }
  142.     return e
  143. }
  144.  
  145. function logical_and(  e, e1) {
  146.     e = inclusive_or()
  147.     while (tok == "&&") {
  148.         advance()
  149.         e1 = inclusive_or()
  150.         e = e && e1
  151.     }
  152.     return e
  153. }
  154.  
  155. function bitwise(a, b, op,  abit, bbit, asign, bsign, rbit, r, t, n) {
  156.     a = int(a)
  157.     asign = (a < 0) ? 1 : 0;
  158.     b = int(b)
  159.     bsign = (b < 0) ? 1 : 0;
  160.     r = 0
  161.     rpos = 1
  162.     for (n = 0; n < 32; ++n) {
  163.         t = int((a-asign)/2)
  164.         abit = a != t+t
  165.         a = t
  166.         t = int((b-bsign)/2)
  167.         bbit = b != t+t
  168.         b = t
  169.         if (op == "|")
  170.             rbit = abit || bbit
  171.         else if (op == "&")
  172.             rbit = abit && bbit
  173.         else if (op == "^")
  174.             rbit = abit != bbit
  175.         else # unary ~
  176.             rbit = !bbit
  177.         r += rpos*rbit
  178.         rpos += rpos
  179.     }
  180.     return r
  181. }
  182.  
  183. function inclusive_or(  e, e1) {
  184.     e = exclusive_or()
  185.     while (tok == "|") {
  186.         advance()
  187.         e1 = exclusive_or()
  188.         e = bitwise(e, e1, "|");
  189.     }
  190.     return e
  191. }
  192.  
  193. function exclusive_or(  e, e1) {
  194.     e = and()
  195.     while (tok == "^") {
  196.         advance()
  197.         e1 = and()
  198.         e = bitwise(e, e1, "^");
  199.     }
  200.     return e
  201. }
  202.  
  203. function and(  e, e1) {
  204.     e = equality()
  205.     while (tok == "&") {
  206.         advance()
  207.         e1 = equality()
  208.         e = bitwise(e, e1, "&");
  209.     }
  210.     return e
  211. }
  212.  
  213. function equality(  op, e, e1) {
  214.     e = relational()
  215.     while (tok == "==" || tok == "!=") {
  216.         op = tok
  217.         advance()
  218.         e1 = relational()
  219.         if (op == "==")
  220.             e = e == e1
  221.         else
  222.             e = e != e1
  223.     }
  224.     return e
  225. }
  226.  
  227. function relational(  op, e, e1) {
  228.     e = shift()
  229.     while (tok ~ /<|<=|>=|>/) {
  230.         op = tok
  231.         advance()
  232.         e1 = shift()
  233.         if (op == "<")
  234.             e = e < e1
  235.         else if (op == "<=")
  236.             e = e <= e1
  237.         else if (op == ">=")
  238.             e = e >= e1
  239.         else
  240.             e = e > e1
  241.     }
  242.     return e
  243. }
  244.  
  245. function shift(  op, e, e1) {
  246.     e = additive()
  247.     while (tok == "<<" || tok == ">>") {
  248.         op = tok
  249.         advance()
  250.         e1 = additive()
  251.         if (op == ">>")
  252.             e1 = -e1
  253.         if (e1 > 0) {
  254.             for (e1 = int(e1); e1 > 0; --e1)
  255.                 e *= 2;
  256.         } else {
  257.             for (e1 = int(-e1); e1 > 0; --e1)
  258.                 e /= 2;
  259.         }
  260.     }
  261.     return e
  262. }
  263.  
  264. function additive(  op, e, e1) {
  265.     e = multiplicative()
  266.     while (tok == "+" || tok == "-") {
  267.         op = tok
  268.         advance()
  269.         e1 = multiplicative()
  270.         if (op == "+")
  271.             e = e + e1
  272.         else
  273.             e = e - e1
  274.     }
  275.     return e
  276. }
  277.  
  278. function multiplicative(  op, e, e1) {
  279.     e = unary()
  280.     while (tok == "*" || tok == "/" || tok == "%") {
  281.         op = tok
  282.         advance()
  283.         e1 = unary()
  284.         if (op == "*")
  285.             e = e * e1
  286.         else if (op == "/")
  287.             e = e / e1
  288.         else
  289.             e = e % e1
  290.     }
  291.     return e
  292. }
  293.  
  294. function unary() {
  295.     if (tok == "-") {
  296.         advance()
  297.         return -primary()
  298.     } else if (tok == "~") {
  299.         advance()
  300.         return bitwise(0, primary(), "~")
  301.     } else if (tok == "!") {
  302.         advance()
  303.         return !primary()
  304.     } else if (tok == "+") {
  305.         advance()
  306.         return primary()
  307.     } else
  308.         return primary()
  309. }
  310.  
  311. function primary(  e) {
  312.     if (tok == "(") {
  313.         advance()
  314.         e = expression()
  315.         eat(")")
  316.         return e
  317.     }
  318.  
  319.     if (tok ~ /^0[xX][0-9a-fA-F]+/) {
  320.         e = gethex(tok)
  321.         advance()
  322.         return e+0
  323.     }
  324.  
  325.     if (tok ~ /^[.0-9]+/) {
  326.         e = tok
  327.         advance()
  328.         return e+0
  329.     }
  330.  
  331.     error(fname "(" lineno ") unexpected \"" tok "\"")
  332. }
  333.  
  334. function gethex(tok) {
  335.     n = length(tok)
  336.     e = 0
  337.     for (i = 3; i <= n; ++i) {
  338.         c = substr(tok,i,1)
  339.         if (c in hextab)
  340.             c = hextab[c]
  341.         else
  342.             error(fname "(" lineno ") bad hex number \"" tok "\"")
  343.         e = e*16 + c
  344.     }
  345.     return (e)
  346. }
  347.